#!/usr/bin/env python
import sys
from math import sin,cos,sqrt
from ctypes import *
from opencv.cv import *
from opencv.highgui import *

class hough(object):
	def __init__(self, image):
		self.image = image
		self.lines = 0
		
	def getCircle(self):
		dst = cvCreateImage(cvGetSize(self.image), 8, 1)
		color_dst = cvCreateImage(cvGetSize(self.image), 8, 3)
		storage = cvCreateMemStorage(0)
		circles = None
		cvCanny(self.image, dst, 50, 200, 3)
		cvCvtColor(dst, color_dst, CV_GRAY2BGR)
		cvSmooth(dst, dst, CV_GAUSSIAN, 9, 9)

		circles = cvHoughCircles(dst, storage, CV_HOUGH_GRADIENT, 2, dst.height/4, 20, 10, 2, 12)
		circle_arr = cvGetSeqElem(circles, 0)
		
		
		print "circles: %s" % circle_arr
		return circle_arr

	def getStandard(self):
		dst = cvCreateImage( cvGetSize(self.image), 8, 1 )
		color_dst = cvCreateImage( cvGetSize(self.image), 8, 3 )
		storage = cvCreateMemStorage(0)
		lines = 0
		cvCanny( self.image, dst, 50, 200, 3 )
		cvCvtColor( dst, color_dst, CV_GRAY2BGR )

		lines = cvHoughLines2( dst, storage, CV_HOUGH_STANDARD, 1, CV_PI/180, 100, 0, 0 )
		lines_arr = lines.asarrayptr(POINTER(c_float))

		for i in range(min(lines.total, 100)):
			line = lines_arr[i]
			rho = line[0]
			theta = line[1]
			pt1 = CvPoint()
			pt2 = CvPoint()
			a = cos(theta)
			b = sin(theta)
			x0 = a*rho 
			y0 = b*rho
			pt1.x = cvRound(x0 + 1000*(-b))
			pt1.y = cvRound(y0 + 1000*(a))
			pt2.x = cvRound(x0 - 1000*(-b))
			pt2.y = cvRound(y0 - 1000*(a))
			cvLine( color_dst, pt1, pt2, CV_RGB(255,0,0), 3, 8 )
	        self.color_dst=color_dst
		self.lines = lines.asarrayptr(POINTER(CvPoint))
	
	def getProbabilistic(self):
		dst = cvCreateImage( cvGetSize(self.image), 8, 1 )
		color_dst = cvCreateImage( cvGetSize(self.image), 8, 3 )
		storage = cvCreateMemStorage(0)
		lines = 0
		cvCanny( self.image, dst, 50, 200, 3 )
		cvCvtColor( dst, color_dst, CV_GRAY2BGR )

		lines = cvHoughLines2( dst, storage, CV_HOUGH_PROBABILISTIC, 1, CV_PI/180, 50, 100, 10 )
		
		self.lines = []
		for line in lines.asarrayptr(POINTER(CvPoint)):
			self.lines.append([[line[0].x, line[0].y], [line[1].x, line[1].y]])
			cvLine( color_dst, line[0], line[1], CV_RGB(255,0,0), 3, 8 )

		self.color_dst = color_dst
		
	def drawLines(self, lines):
		dst = cvCreateImage( cvGetSize(self.image), 8, 1 )
		color_dst = cvCreateImage( cvGetSize(self.image), 8, 3 )
		storage = cvCreateMemStorage(0)
		cvCanny( self.image, dst, 50, 200, 3 )
		cvCvtColor( dst, color_dst, CV_GRAY2BGR )
		
		for line in lines:
			cvLine( color_dst, self.toCvLine(line[0]), self.toCvLine(line[1]), CV_RGB(0,255,0), 3, 8 )
		self.color_dst = color_dst


	def drawBoxes(self, boxes):
		dst = cvCreateImage( cvGetSize(self.image), 8, 1 )
		color_dst = cvCreateImage( cvGetSize(self.image), 8, 3 )
		storage = cvCreateMemStorage(0)
		cvCanny( self.image, dst, 50, 200, 3 )
		cvCvtColor( dst, color_dst, CV_GRAY2BGR )
		
		for box in boxes:
			cvRectangle(color_dst, box[0], box[1], CV_RGB(255, 0, 0), 2)
		self.color_dst = color_dst
			
	def toCvLine(self, point):
		return CvPoint(point[0], point[1])

	def showImage(self):
		cvNamedWindow( "Hough", 1 )
		cvShowImage( "Hough", self.color_dst )
		cvWaitKey(0)
		
		


